package com.symphony.serialization;

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
import java.io.Writer;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Set;

import org.json.JSONArray;
import org.json.JSONObject;

public class Serializer {
	
	public static JSONObject createReportsJsonFromMap(Map<String, List<Report>> reports) {
		JSONObject mainReportsObject = new JSONObject();
		JSONArray eventsArray = new JSONArray();

		Set<Entry<String, List<Report>>> s = reports.entrySet();
		Iterator<Entry<String, List<Report>>> i = s.iterator();
		while (i.hasNext()) {
			Entry<String, List<Report>> currEntry = i.next();
			
			String eventName = currEntry.getKey();
			List<Report> currReports = currEntry.getValue();
			
			JSONObject event = new JSONObject();
			
			event.put(eventName, createJSONArrayFromListReports(currReports));
			
			eventsArray.put(event);
		}
		
		mainReportsObject.put("events", eventsArray);
		
		return mainReportsObject;
	}
	
	public static JSONArray createJSONArrayFromListReports(List<Report> reports) {
		JSONArray array = new JSONArray();
		
		for (int i = 0; i < reports.size(); i++) {
			Report r = reports.get(i);
			JSONObject o = new JSONObject();
			o.put("timestamp", r.getTime());
			array.put(o);
		}
		
		return array;
	}
	
	public static Map<String, List<Report>> createEventsMapFromJsonObject(JSONObject eventsJson) {
		Map<String, List<Report>> eventsMap = new HashMap<String, List<Report>>();
		
		JSONArray eventsJsonArray = eventsJson.getJSONArray("events");
		
		for (int i = 0; i < eventsJsonArray.length(); i++) {
			JSONObject eventJsonObject = eventsJsonArray.getJSONObject(i);
			Iterator<String> iterator = eventJsonObject.keys();
			String eventName = "";
			List<Report> reports = new ArrayList<Report>();
			if (iterator.hasNext()) {
				eventName = iterator.next();
			} else {
				//TODO handle the situation
			}
			
			JSONArray reportsArray = eventJsonObject.getJSONArray(eventName);
			for (int j = 0; j < reportsArray.length(); j++) {
				JSONObject currReportJson = reportsArray.getJSONObject(j);
				Report currReport = createReportFromJsonObject(currReportJson); 
				reports.add(currReport);
			}
			eventsMap.put(eventName, reports);
		}
		
		return eventsMap;
	}
	
	public static Report createReportFromJsonObject(JSONObject reportJson) {
		Report report = new Report(reportJson.getLong("timestamp"));
		return report;
	}
	
	public static void writeJsonToFile(String path, JSONObject json) {
		try {
			File file = new File(path);
			Writer w = new FileWriter(file);
			BufferedWriter bw = new BufferedWriter(w);
			bw.write(json.toString());
			bw.flush();
		} catch(IOException e) {
			e.printStackTrace();
		}
	}
	
	public static JSONObject readJsonFromFile(String path) {
		String source = "";
		StringBuilder sourcebuBuilder = new StringBuilder();
		BufferedReader reader = null;
		try {
			File file = new File(path);
			FileReader fileReader = new FileReader(file);
			reader = new BufferedReader(fileReader);
			String buf = "";
			while ((buf = reader.readLine()) != null) {
				sourcebuBuilder.append(buf);
			}
			source = sourcebuBuilder.toString();
		} catch(IOException e) {
			e.printStackTrace();
		}
		return new JSONObject(source);
	}
}
